/**
    ATClab - scriptable Air Traffic Control simulations.
    Copyright (C) 2010 openatclab@gmail.com

    This program is free software: you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation, either version 3 of the License, or
    (at your option) any later version.

    This program is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with this program.  If not, see <http://www.gnu.org/licenses/>.
**/

#ifndef __ATC_ENGINE_IMPL_HDR__ 
#define __ATC_ENGINE_IMPL_HDR__


#ifdef WIN32
	#pragma warning( disable:4786 )
#endif


#include "engine.h"

#include "param_impl.h"
#include "map_impl.h"
#include "sky_impl.h"
#include "taskfactory.h"
#include <qmatrix.h>
#include <memory>
#include <stdexcept>

//
// Qt classes
//

class QTime;


namespace atc{

	//
	// atc classes
	//
	class Airspace;
	class Canvas;
	class Clock;
	class LabEngine;


	/*!
	 */
	struct AircraftData;
	class  AircraftPath;

	class Transformation;


	/*!
	 * \struct engine_error
	 */
	struct engine_error : public std::runtime_error{
		engine_error(const std::string& msg) : std::runtime_error(msg){}
	};


	/*!
	 * \class EngineImpl
	 * \brief Implementation of the atc::Engine interface
	 */
	class EngineImpl : public Engine {
		Q_OBJECT

	public:
		EngineImpl(pact::TrialTaskType a_type = pact::TRIAL_TASK_NORMAL);
		~EngineImpl();

	public: // [new]
		void build();
		pact::TrialTaskType Type() const { return m_type; }

	public: // engine interface
		Param& param();
		Map& map();
		Sky& sky();
		
		QWidget* create_view( QWidget *, const char * );

		virtual void set_alarm( int, QObject *, const char * );

	public: // new engine api
		void add_aircraft( const AircraftData &, const AircraftPath &, unsigned int );
		void add_scale_tool( GridPosition );

		Score*	get_score() { return _score; }
		long	ElapsedTimeSec() const;

	public slots: // engine interface
		void init();
		void start();
		void stop();
		void reset() {};
		void clear() {};

	private:
		//params
		void process_params();

		//map
		void process_map();
		void process_sectors( const SectorMap & );
		void process_sector( const SectorDefinition );
		void process_routes( const RouteMap & );
		void process_locations( const LocationMap & );

		//sky
		void process_sky();
		void process_aircraft(const AircraftParam&);

		// general
//		QPointArray& area_points( const AreaDefinition &, QPointArray & ); 

	signals:
		void sig_engine_stopped();
		void sig_engine_resumed();
		
	private: // members [old]
		ParamImpl      *_params;
		MapImpl        *_map;
		SkyImpl        *_sky;
		// nb: removed autoptrs because they were being misused (which causes problems on modern compilers.)
		Airspace   * _airspace;
		Canvas     * _canvas; 
		Clock      * _clock;
		LabEngine  * _atclab;

	private:
		Score *_score;
		pact::TrialTaskType m_type;
	};

}

#endif
